<?php

class ObjectController extends Silk_Controller_Admin_Action {

    protected $action = null;

    public function init(){
	parent::init();

	if ($this->_request->has('template'))
	    $this->action = strtolower($this->_getParam('template'));
	else
	    $this->action = 'view';

    }

    public function listwidgetAction(){

	$type = $this->_getParam('type');

	if ($type instanceof Silk_Type)
	    $type_id = $type->type_id;
	else if (is_numeric($type)){
	    $Types = new Silk_Types();
	    $type = $Types->fetch($type);
	    $type_id = $type->type_id;
	}

	$this->initPaginatorParams('object-list-widget-' . $type->slug, 'updated_at', 'DESC', 10);

	$session = Silk::getSession();

	$Objects = new Silk_Objects();
	$site = Silk::getCurrentSite();

	$session->criteria = array(
	    'type_id' => $type_id,
	    'site_id' => $site->site_id
	);

	$paginator = $Objects->getPaginator($session->criteria, "{$session->sort} {$session->order}");

	$paginator->setItemCountPerPage($session->limit);
	$paginator->setCurrentPageNumber($session->page);

	$this->view->objects = $paginator;
    }

    public function permissionsAction(){

	if ($this->_request->has('object')){
	    $object = $this->_getParam('object');
	    if (!($object instanceof Silk_Object)){
		$Objects = new Silk_Objects();
		$object  = $Objects->fetch($object);
	    }
	} else if ($this->_request->has('object_id')){
	    $Objects = new Silk_Objects();
	    $object  = $Objects->fetch($this->_getParam('object_id'));
	} else
	    throw new FP_Route_Exception('Invalid object', FP_Route_Exception::NO_RESOURCE);

	if ($this->_request->isPost()){
	    logdebug("ObjectController.permissionsAction: Request is POST");
	    $this->disableLayout();

	    if (strtolower($this->_getParam('submit')) == 'cancel'){
		$this->render('close-permissions');
	    } else {
		$role_permissions = ($this->_getParam('role_permissions')) ? $this->_getParam('role_permissions') : array();
		$user_permissions = ($this->_getParam('user_permissions')) ? $this->_getParam('user_permissions') : array();

		$Objects = new Silk_Objects();
		$Objects->setPermissions($object, $role_permissions, $user_permissions);

		$this->render('close-permissions');
	    }
	} else {
	    logdebug("ObjectController.permissionsAction: Request is GET");
 	    if ($this->_request->has('lb'))
		$this->setLayout('lightbox');

	    $permissions = $object->getPermissions();
	    $privileges = array();

	    foreach ($permissions as $permission){
		if ($permission->privilege != PERMISSION_CREATE)
		    if (!in_array($permission->privilege, $privileges))
			$privileges[] = $permission->privilege;
	    }

	    if (!in_array(PERMISSION_EDIT, $privileges))
		$privileges[] = PERMISSION_EDIT;

	    if (!in_array(PERMISSION_VIEW, $privileges))
		$privileges[] = PERMISSION_VIEW;

	    if (!in_array(PERMISSION_DELETE, $privileges))
		$privileges[] = PERMISSION_DELETE;

	    asort($privileges);

	    $Roles = new Silk_Roles();

	    $owner = $object->getUser();
	    logdebug("ObjectController.permissionsAction: object={$object->object_id} owner={$owner->user_id}");

	    $this->view->resource = $object->getResourceName();
	    $this->view->owner = $owner;
	    $this->view->roles = $Roles->fetch();
	    $this->view->privileges = $privileges;
	    $this->view->object = $object;
	    $this->view->permissions = $permissions;
	    $this->view->users = array();

	    $this->view->suppress_form = ($this->_request->has('suppress_form')) ? true: false;


// 	    logdebug("ObjectController.permissionsAction: Resource var = {$this->view->resource}");
	}

    }

    public function renderAction(){

	$Objects = new Silk_Objects();
	if ($this->_request->has('_object_id')){
	    $object = $Objects->fetch($this->_getParam('_object_id'));
	} else if ($this->_request->has('object')){
	    if ($this->_getParam('object') instanceof Silk_Object)
		$object = $this->_getParam('object');
	    else
		throw new FP_Route_Exception('Invalid object', FP_Route_Exception::NO_RESOURCE);
	} else if ($this->_request->has('object_id')){
		$object = $Objects->fetch($this->_getParam('object_id'));
	} else
	    throw new FP_Route_Exception('Invalid object id', FP_Route_Exception::NO_RESOURCE);

	if ($object){

	    if (!$this->_request->has('object'))
		$params = array_merge($this->_getAllParams(), array('object' => $object));
	    else
		$params = $this->_getAllParams();

	    switch ($this->action){
		case 'edit':
		    return $this->_forward('edit', null, null, $params);
		case 'delete':
		    return $this->_forward('delete', null, null, $params);
		case 'permissions':
		    return $this->_forward('permissions', null, null, $params);
		case 'view':
		    return $this->_forward('view', null, null, $params);
	    }

	    try {
		$this->disableView();
//  		logdebug('Controller_Object.action_render: Object=' . $object->object_id . ' Action=' . $this->action . ' Params=' . logobject($params));

		Silk::triggerHook('object-pre-render', $object, $this->action);

		$output = $object->render($this->action, $params);
		$this->_response->setBody($output);
	    } catch (Exception $x){
		logexception($x);
		throw $x;
	    }
	} else
	    throw new FP_Route_Exception('Invalid object id', FP_Route_Exception::NO_RESOURCE);


    }

    public function adminAction(){
	$type = $this->_getParam('type');

	if ($type){
	    if ($type instanceof Silk_Type)
		$mtype = $type->getModuleType();
	    else {
		$Types = new Silk_Types();
		$type  = $Types->getModelObject($type);
		if (!$type)
		    throw new Silk_Exception('Invalid type');
		$mtype = $type->getModuleType();
	    }

 	    $output = $mtype->render(null, 'admin');
// 	    $output = $type->render(null, 'admin');
	    $this->_response->setBody($output);
	    $this->disableView();
	} else
	    throw new Silk_Exception('Type not specified');
    }


    public function createAction(){
	$type = $this->_getParam('type');

	if ($type){

	    $Types   = new Silk_Types();
	    $type    = $Types->getModelObject($type);

	    $object  = $Types->instantiate($type, $this->getCleanParams());

	    if ($this->_request->isPost()){
 		if ($this->_request->has('submit') && strtolower($this->_getParam('submit')) == 'cancel')
		    $this->gotoRoute('dashboard');

		try {
		    Silk::triggerHook('object-pre-create', &$object);

		    $object->import($this->_getParam('object'));
		    $object->save();

		    $role_permissions = ($this->_getParam('role_permissions')) ? $this->_getParam('role_permissions') : array();
		    $user_permissions = ($this->_getParam('user_permissions')) ? $this->_getParam('user_permissions') : array();

		    $Objects = new Silk_Objects();
		    $Objects->setPermissions($object, $role_permissions, $user_permissions);

		    $user =& Silk::getIdentity();
		    if ($user) $user->flushPermissions();

		    Silk::triggerHook('object-post-save', &$object);
		    Silk::triggerHook('object-post-create', &$object);

		    $this->gotoRoute('object_admin', array('type' => $object->getType()->slug));
		} catch (FP_Validation_Exception $x){
		    throw $x;
		}

	    } else {
		Silk::triggerHook('object-pre-render', &$object, 'create');

// 		$permissions = $type->getPermissions();
//
// 		$privileges = array();
//
// 		foreach ($permissions as $permission){
// 		    if (!in_array($permission->privilege, $privileges))
// 			$privileges[] = $permission->privilege;
// 		}
		logdebug('ObjectController.createAction', 'Rendering create');
		$output = $object->render('create');
		logdebug('ObjectController.createAction', 'Rendered create');
		$this->_response->setBody($output);
		$this->disableView();
	    }

	} else
	    throw new Silk_Exception('Type not specified');
    }

    public function viewAction(){
	logdebug('ObjectController.viewAction: Called');

	if ($this->_request->has('object')){
	    $object = $this->_getParam('object');
	    if ($object->hasPermission(PERMISSION_VIEW)){

		Silk::triggerHook('object-pre-view', &$object);
		Silk::triggerHook('object-pre-render', &$object, 'view');
		$output = $object->render('view');
		$this->_response->setBody($output);
		$this->disableView();
	    } else
		throw new FP_Acl_Exception('Insufficient privileges to view this object', FP_Acl_Exception::ACCESS_DENIED);
	} else
	    throw new FP_Route_Exception('Invalid object id', FP_Route_Exception::NO_RESOURCE);
    }

    public function editAction(){
	if ($this->_request->has('object') && $this->_getParam('object') instanceof Silk_Object) {
	    $object = $this->_getParam('object');

	} else if ($this->_request->has('object_id')){
	    $Objects = new Silk_Objects();
	    $object  = $Objects->fetch($this->_getParam('object_id'));

	}

	if ($object){
	    if ($object->hasPermission(PERMISSION_EDIT)){

		if ($this->_request->isPost()){
		    if ($this->_request->has('submit') && strtolower($this->_getParam('submit')) == 'cancel')
			$this->gotoRoute('dashboard');

		    Silk::triggerHook('object-pre-edit', &$object);
		    $object->import($this->_getParam('object'));
		    $object->save();

		    $role_permissions = ($this->_getParam('role_permissions')) ? $this->_getParam('role_permissions') : array();
		    $user_permissions = ($this->_getParam('user_permissions')) ? $this->_getParam('user_permissions') : array();
		    $Objects->setPermissions($object, $role_permissions, $user_permissions);

		    $user =& Silk::getIdentity();
		    if ($user) $user->flushPermissions();

		    Silk::triggerHook('object-post-edit', &$object);
		    $this->gotoRoute('object_admin', array('type' => $object->getType()->slug));
		} else {
		    Silk::triggerHook('object-pre-render', &$object, 'edit');
		    $output = $object->render('edit');
		    $this->_response->setBody($output);

		}
		$this->disableView();
	    } else
		throw new FP_Acl_Exception('Insufficient privileges to view this object', FP_Acl_Exception::ACCESS_DENIED);
	} else
	    throw new FP_Route_Exception('Invalid object id', FP_Route_Exception::NO_RESOURCE);
    }

    public function deleteAction(){
	if ($this->_request->has('object') && $this->_getParam('object') instanceof Silk_Object){
	    $object = $this->_getParam('object');

	} else if ($this->_request->has('object_id')){
	    $Objects = new Silk_Objects();
	    $object  = $Objects->fetch($this->_getParam('object_id'));

	}

	if ($object){
	    if ($object->hasPermission(PERMISSION_DELETE)){
		if ($this->_request->isPost()){
		    if ($this->_request->has('submit') && strtolower($this->_getParam('submit')) == 'cancel')
			$this->gotoRoute('dashboard');

		    Silk::triggerHook('object-pre-delete', &$object);
		    logdebug("ObjectController.deleteAction: Calling delete on object [{$object->object_id}]");
		    $object->delete();

		    $user =& Silk::getIdentity();
		    if ($user) $user->flushPermissions();

		    Silk::triggerHook('object-post-delete', &$object);
		    $this->gotoRoute('object_admin', array('type' => $object->getType()->slug));
		} else {
		    Silk::triggerHook('object-pre-render', &$object, 'delete');
		    $output = $object->render('delete');
		    $this->_response->setBody($output);
		    $this->disableView();
		}
	    } else
		throw new FP_Acl_Exception('Insufficient privileges to view this object', FP_Acl_Exception::ACCESS_DENIED);
	} else
	    throw new FP_Route_Exception('Invalid object id', FP_Route_Exception::NO_RESOURCE);
    }
}

?>